package com.moran.test.scala.json

import com.fasterxml.jackson.core.{JsonGenerator, JsonParser}
import com.fasterxml.jackson.databind._
import com.fasterxml.jackson.databind.annotation.{JsonDeserialize, JsonSerialize}
import org.slf4j.LoggerFactory

object Jackson extends App{
  private val mapper = new ObjectMapper()
  private val logger = LoggerFactory.getLogger(classOf[App])

  @JsonSerialize(using = classOf[BookSerializer])
  @JsonDeserialize(using = classOf[BookDeserializer])
  case class Book (id: Int, name: String, price: Float)

  class BookSerializer extends JsonSerializer[Book] {
    override def serialize(book: Book, jgen: JsonGenerator, provider: SerializerProvider): Unit = {
      jgen.writeStartObject()

      jgen.writeFieldName("id")
      jgen.writeNumber(book.id)

      jgen.writeFieldName("name")
      jgen.writeString(book.name)

      jgen.writeFieldName("price")
      jgen.writeNumber(book.price)

      jgen.writeEndObject()
    }
  }

  class BookDeserializer extends JsonDeserializer[Book]{
    override def deserialize(jsonParser: JsonParser, deserializationContext: DeserializationContext): Book = {
      val node:JsonNode = jsonParser.getCodec.readTree(jsonParser)
      val id:Int = node.get("id").intValue()
      val name:String = node.get("name").textValue()
      val price:Float = node.get("price").floatValue()
      Book(id,name,price)
    }
  }

  val bookOut = Book(5, "从入门到放弃", 70)

  val bookJson = mapper.writeValueAsString(bookOut)

  logger.info(bookJson)

  val bookIn = mapper.readValue(bookJson,classOf[Book])

  //Output only when the log level is less than or equal to debug
  logger.debug(bookIn.name)
}
